/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package EntidadesController;

import Criptografia.BlowFish;
import java.sql.*;
import java.util.ArrayList;
import java.util.List;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.faces.context.FacesContext;
import javax.faces.event.ValueChangeEvent;
import javax.swing.JOptionPane;

public class Docente {

    private String matriculadoc = "";
    private String usuario_login = "";
    private String departamento_codigodep = "";
    private String nome = "";
    private String ano;
    private String mes;
    private String dia;
    private String unidade;
    private String nota;
    private String email = "";
    private String grupo = "Docente";
    private String senha = "";
    private String turma = "";
    private String aluno = "";
    private String matriculadisc = "";
    private String texto = "";
    private String tipo = "";
    private SQLException erro = new SQLException();
    static Connection conexao2 = null;
    static Statement estado2 = null;
    private List<String> tipoNotificacao;
    static Connection conexao = null;
    static Statement estado = null;
    static ResultSet rs;
    static ResultSet rs2;
    private String cript;
    private List<Falta> listaFaltas;
    private List<Avaliacao> listaNotas;
    public List<String> listaNome;
    public List<String> listaMatricula;
    private List<String> listaIdTurmaDiscente;
    private boolean render=false;
    private boolean render2=false;
    private boolean render3=false;
    private String msgerro;
    private String msgerro2;
    private String msgerro3;

    public String getMsgerro3() {
        return msgerro3;
    }

    public void setMsgerro3(String msgerro3) {
        this.msgerro3 = msgerro3;
    }

    public boolean isRender3() {
        return render3;
    }

    public void setRender3(boolean render3) {
        this.render3 = render3;
    }


    public String getMsgerro2() {
        return msgerro2;
    }

    public void setMsgerro2(String msgerro2) {
        this.msgerro2 = msgerro2;
    }

    public boolean isRender2() {
        return render2;
    }

    public void setRender2(boolean render2) {
        this.render2 = render2;
    }



    public boolean isRender() {
        return render;
    }

    public void setRender(boolean render) {
        this.render = render;
    }

    public String getMsgerro() {
        return msgerro;
    }

    public void setMsgerro(String msgerro) {
        this.msgerro = msgerro;
    }

    public Docente() {
        conexao = new Conexao().Acesso();
        this.tipoNotificacao = new ArrayList<String>();
        this.tipoNotificacao.add("Informes");
        this.tipoNotificacao.add("Mudanca de sala");
    }

    public String inserir() throws SQLException {
        String result_inserir = "failure";
        /*CREATE TABLE docente (matriculadoc varchar, usuario_login VARCHAR,
        departamento_codigodep varchar,  nome varchar(30), CONSTRAINT pk_matriculadoc PRIMARY KEY (matriculadoc)*/
        try {
            estado = conexao.createStatement();
            estado.execute("BEGIN WORK");

            estado.execute("INSERT INTO Usuario(usrlogin,senha,grupo_grupo) VALUES ('" + usuario_login + "','"
                    + senha + "','" + grupo + "')");
            //criar docente
            estado.execute("INSERT INTO docente(matriculadoc, usuario_usrlogin, departamento_codigodep,"
                    + "nome,email) VALUES ('" + matriculadoc + "','" + usuario_login + "','" + departamento_codigodep
                    + "','" + nome + "','" + email + "')");

            estado.execute("COMMIT");
            estado.close();
            result_inserir = "success";
            render = false;
        } catch (SQLException e) {
            this.erro = e;

            msgerro = erro.getLocalizedMessage();

            if (msgerro.contains("pk_matriculadoc")&&msgerro.contains("unicidade"))
            {msgerro = "Esse número de matrícula ja está cadastrado!";}

            //if (msgerro.contains("un_celular")&&msgerro.contains("unicidade"))
            //{msgerro = "Esse número de telefone ja está cadastrado!";}

            if (msgerro.contains("pk_id")&&msgerro.contains("unicidade"))
            {msgerro = "Esse login ja está cadastrado!";}
            estado.execute("ROLLBACK");
            estado.close();
            result_inserir = "failure";
            render = true;
        }
        return result_inserir;
    }

    //A busca utilizará a matricula e login!!!!!
    public String buscar() throws SQLException {
        String result_busca = "failure";
        try {
            estado = conexao.createStatement();
            rs = estado.executeQuery("SELECT * FROM docente WHERE usuario_usrlogin = '" + this.usuario_login + "'");
            if (rs.next()) {
                this.matriculadoc = rs.getString(1);
                departamento_codigodep = rs.getString(3);
                nome = rs.getString(4);
                email = rs.getString(5);
            }
            rs.close();
            System.out.println("Nome: " + nome);
            result_busca = "success";
            estado.close();
        } catch (SQLException e) {
            this.erro = e;
            estado.close();
            result_busca = "failure";
        }
        return result_busca;
    }

    //Apenas para saber se o login é valido ou não!!!!!
    public String validarLogin() throws SQLException {
        String resultado;
        Usuario u = new Usuario();
        u.setGrupo("docente");
        u.setLogin(usuario_login);
        u.setSenha(senha);
        resultado = u.validar();
        if (resultado.compareTo("success") == 0) {
            resultado = buscar();
        }
        return resultado;
    }

    public String editar() throws SQLException {
        String result_editar = "failure";
        /*CREATE TABLE docente (matriculadoc varchar, usuario_login VARCHAR, celular_ddd varchar(2), celular_num varchar(8),
        departamento_codigodep varchar,  nome varchar(30), CONSTRAINT pk_matriculadoc PRIMARY KEY (matriculadoc)*/
        try {
            estado = conexao.createStatement();
            //docente(matriculadoc, usuario_login, departamento_codigodep,nome,email)
            estado.execute("BEGIN WORK");

            estado.execute("update docente set departamento_codigodep = '" + departamento_codigodep + "' where matriculadoc ='" + matriculadoc + "'");
            estado.execute("update docente set nome = '" + nome + "' where matriculadoc ='" + matriculadoc + "'");
            estado.execute("update docente set email = '" + email + "' where matriculadoc ='" + matriculadoc + "'");
            //naum sera' editado grupo nem login
            estado.execute("update usuario set senha = '" + senha + "' where usrlogin ='" + usuario_login + "'");

            estado.execute("COMMIT");
            estado.close();
            result_editar = "success";
            matriculadoc = "";
            departamento_codigodep = "";
            nome = "";
            email = "";
        } catch (SQLException e) {
            this.erro = e;
            estado.execute("ROLLBACK");
            estado.close();
            result_editar = "failure";
        }
        return result_editar;
    }

    //Metodo criado por João Gabriel.
    //Esse método busca um professor
    //no banco de dados pelo seu número de
    //matricula. Retorna a string "success"
    //caso a busca tenha sido concluida com
    //sucesso e "failure" caso não tenha encontrado nada.
    public String buscarProfessor(){
        String result = "failure";

        try{
            estado = conexao.createStatement();
            rs = estado.executeQuery("SELECT * FROM docente WHERE matriculadoc = '"+ matriculadoc +"'");
            if (rs.next()){
                matriculadoc = rs.getString(1);
                departamento_codigodep = rs.getString(3);
                nome = rs.getString(4);
                email = rs.getString(5);
            }
            rs.close();
            result = "success";
            estado.close();

        }catch(SQLException e){
            this.erro = e;
            result = "failure";
        }
        return result;
    }

    //Para dar mais segurança pra deletar é necessário saber o login e a matricula
    public String delete() throws SQLException {
        String result_delete = "failure";
        try {
            estado = conexao.createStatement();
            estado.executeQuery("DELETE FROM docente WHERE matriculadoc = '" + this.matriculadoc + "' "
                    + "and usuario_usrlogin = '" + usuario_login + "'");
            estado.executeQuery("DELETE FROM usuario WHERE usrlogin = '" + usuario_login + "'");
            estado.close();
        } catch (SQLException e) {
            this.erro = e;
            estado.close();
            result_delete = "failure";
        }
        return result_delete;
    }

    public String getGrupo() {
        return grupo;
    }

    public String getSenha() {
        return senha;
    }

    public void setSenha(String senha) {
        senha = senha.toLowerCase();
        cript = BlowFish.cript(senha, usuario_login);
        this.senha = cript;
    }

    public String getDepartamento_codigodep() {
        return departamento_codigodep;
    }

    public List<String> getcodigodep() throws SQLException {

        List<String> items = new ArrayList<String>();

        estado = conexao.createStatement();
        rs = estado.executeQuery("SELECT * FROM departamento");
        while (rs.next() == true) {
            items.add(rs.getString(1));
        }
        return items;
    }

    public String getErro() {
        return erro.getMessage();
    }

    public void setDepartamento_codigodep(String departamento_codigodep) {
        this.departamento_codigodep = departamento_codigodep;
    }

    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }

    public String getMatriculadoc() throws SQLException {

        return matriculadoc;
    }

    public void setMatriculadoc(String matriculadoc) {
        this.matriculadoc = matriculadoc;
    }

    public String getNome() {
        return nome;
    }

    public void setNome(String nome) {
        this.nome = nome;
    }

    public String getUsuario_login() {
        return usuario_login;
    }

    public void setUsuario_login(String usuario_login) {
        this.usuario_login = usuario_login;
    }

    public String getTurma() {
        return turma;
    }

    public void setTurma(String turma) {
        this.turma = turma;
    }

    public String getAluno() {
        return aluno;
    }

    public void setAluno(String aluno) {
        this.aluno = aluno;
    }

    public List<String> getListaNome() {
        return listaNome;
    }

    public void setListaNome(List<String> lista) {
        this.listaNome = lista;
    }

    public List<String> getTipoNotificacao() {
        return this.tipoNotificacao;
    }
    public String geraDocente() throws SQLException
    {
        Docente docente = (Docente) FacesContext.getCurrentInstance().getExternalContext().getSessionMap().get("docente");
        this.usuario_login = docente.usuario_login;
        this.buscar();
        return this.nome;
        
    }
//
//    public void setTipoNotificacao(List<String> listaTipoNotifi) {
//        this.lista = listaTipoNotifi;
//    }

    /*
     * Este metodo retorna uma lista de strings, necessaria para exibir
     * a combobox na interface com o usuario e nao toda a tabela.
     */
    public List<String> getListaTurmas() throws SQLException {

        Docente docente;
        List<String> itens = new ArrayList<String>();

        try {

            docente = (Docente) FacesContext.getCurrentInstance().getExternalContext().getSessionMap().get("docente");
            docente.buscar();

            estado = conexao.createStatement();
            //  Obtem da tabela 'Turma', todas as turmas lecionadas por um docente;
            rs = estado.executeQuery("SELECT disciplina_coddisciplina FROM Turma WHERE "
                    + "docente_matriculadoc = '" + docente.matriculadoc + "'");


            while (rs.next() == true) {

                // Primeira coluna da tabela: variavel 'disciplina_coddisciplina';
                if(!itens.contains(new String(rs.getString(1))))
                itens.add(rs.getString(1));
            }
            return itens;

        } catch (SQLException ex) {
            this.erro = ex;
            estado.close();
            System.out.println("A tabela esta vazia.");
            Logger.getLogger(Curso.class.getName()).log(Level.SEVERE, null, ex);
            return null;
        }
    }

    //Metodo criado por João Gabriel para carregar os dados do docente na sua
    //página de perfil.
    public String DadosProfessor(){
        Docente professor;
        String result = "failure";

        try{
            professor = (Docente) FacesContext.getCurrentInstance().getExternalContext().getSessionMap().get("docente");
            professor.buscar();
            this.setNome(professor.getNome());
            this.setEmail(professor.getEmail());
            this.setDepartamento_codigodep(professor.getDepartamento_codigodep());
            this.setMatriculadoc(professor.getMatriculadoc());
            result = "success";

        }catch(SQLException e){
            erro = e;
        }
        return result;
    }

    public List<Falta> ListaAlunosFaltas(String turma) throws SQLException {
        Falta objeto;
        listaMatricula = new ArrayList<String>();
        listaIdTurmaDiscente = new ArrayList<String>();
        listaNome = new ArrayList<String>();
        listaFaltas = new ArrayList<Falta>();
        int a;

        try {
            estado = conexao.createStatement();
            //  Obtem da tabela 'Turma_has_discente' todas os alunos matriculados em uma determinada turma;
            rs = estado.executeQuery("SELECT * FROM Turma_has_discente "
                    + "WHERE turma_disciplina_coddisciplina = '" + turma + "'");

            a = 0;
            while (rs.next() == true) {
                // Quinta coluna da tabela: variavel 'discente_matriculadisc';
                listaMatricula.add(rs.getString(5));
                listaIdTurmaDiscente.add(rs.getString(1));
                //System.out.println("Matrícula: "+rs.getString(5));
            }

            for (a = 0; a < listaMatricula.size(); a++) {
                // Buscar Nomes
                rs2 = estado.executeQuery("SELECT * FROM Discente "
                        + "WHERE matriculadisc = '" + listaMatricula.get(a) + "'");

                while (rs2.next() == true) {
                    listaNome.add(rs2.getString(3));
                }
            }

            for (a = 0; a < listaMatricula.size(); a++) {
                objeto = new Falta();
                //objeto.setAno_ano(ano);
                //objeto.setDia_dia(dia);
                //objeto.setMes_mes(mes);
                objeto.setNome(listaNome.get(a));
                objeto.setMatricula(listaMatricula.get(a));
                objeto.setIdturma_x_discente(listaIdTurmaDiscente.get(a));
                listaFaltas.add(objeto);
            }
            return listaFaltas; // Lista de Objetos de Falta
        } catch (SQLException ex) {
            this.erro = ex;
            estado.close();
            System.out.println("A tabela esta vazia.");
            Logger.getLogger(Curso.class.getName()).log(Level.SEVERE, null, ex);
            return null;
        }
    }

    public List<Avaliacao> ListaAlunosNotas(String turma) throws SQLException {

        Avaliacao objeto;
        listaMatricula = new ArrayList<String>();
        listaIdTurmaDiscente = new ArrayList<String>();
        listaNome = new ArrayList<String>();
        listaNotas = new ArrayList<Avaliacao>();
        int a;

        try {
            estado = conexao.createStatement();
            //  Obtem da tabela 'Turma_has_discente' todas os alunos matriculados em uma determinada turma;
            rs = estado.executeQuery("SELECT * FROM Turma_has_discente "
                    + "WHERE turma_disciplina_coddisciplina = '" + turma + "'");

            a = 0;
            while (rs.next() == true) {
                // Quinta coluna da tabela: variavel 'discente_matriculadisc';
                listaMatricula.add(rs.getString(5));
                listaIdTurmaDiscente.add(rs.getString(1));
            }

            for (a = 0; a < listaMatricula.size(); a++) {
                // Buscar Nomes
                rs2 = estado.executeQuery("SELECT * FROM Discente "
                        + "WHERE matriculadisc = '" + listaMatricula.get(a) + "'");

                while (rs2.next() == true) {
                    listaNome.add(rs2.getString(3));
                }
            }

            for (a = 0; a < listaMatricula.size(); a++) {
                objeto = new Avaliacao();
                objeto.setNome(listaNome.get(a));
                objeto.setMatricula(listaMatricula.get(a));
                objeto.setIdturma_x_discente(listaIdTurmaDiscente.get(a));
                listaNotas.add(objeto);
            }
            return listaNotas; // Lista de Objetos de Avaliacao
        } catch (SQLException ex) {
            this.erro = ex;
            estado.close();
            System.out.println("A tabela esta vazia.");
            Logger.getLogger(Curso.class.getName()).log(Level.SEVERE, null, ex);
            return null;
        }
    }

    public String cadastrarFalta() throws SQLException {


        texto = "Falta adicionada na disciplina: " + turma + " Data: " + dia + "/" + mes + "/" + ano;
        tipo = "Falta";

        try {
            for (int a = 0; a < listaFaltas.size(); a++) {
                if (listaFaltas.get(a).getFalta() == true) {
                    estado = conexao.createStatement();
                    estado.execute("BEGIN WORK");

                    estado.execute("INSERT INTO falta(idturma_x_discente, dia_dia, mes_mes, "
                            + "ano_ano) VALUES ('" + listaFaltas.get(a).getIdturma_x_discenteF() + "','"
                            + dia + "','" + mes + "','" + ano + "')");

                    estado.execute("COMMIT");
                    estado.close();

                    estado = conexao.createStatement();
                    rs = estado.executeQuery("SELECT * FROM turma_has_discente WHERE idturma_has_discente= '" + listaFaltas.get(a).getIdturma_x_discenteF() + "'");
                    if (rs.next()) {
                        matriculadisc = rs.getString(5);
                    }
                    rs.close();
                    estado.close();

                    System.out.println("Teste: " + matriculadisc);

                    System.out.println("Texto: " + texto);

                    Docente docente;

                    docente = (Docente) FacesContext.getCurrentInstance().getExternalContext().getSessionMap().get("docente");
                    docente.buscar();

                    matriculadoc = docente.getMatriculadoc();

                    System.out.println("Matricula docente: " + matriculadoc);

                    estado = conexao.createStatement();

                    estado.execute("INSERT INTO notificacao(discente_matriculadisc, tipo_notif_tiponotificacao, docente_matriculadoc, texto) VALUES ('"
                            + matriculadisc + "','" + tipo + "','" + matriculadoc + "','" + texto + "')");

                    estado.close();
                }
            }
            render3 = false;
            return "success";
        } catch (SQLException e) {
            this.erro = e;
            msgerro3 = erro.getLocalizedMessage();
            if (msgerro3.contains("fk_tipo_notif_tiponotificacao")&&msgerro3.contains("notificacao")&&msgerro3.contains("Falta"))
            {msgerro3 = "A notificação para inserção de faltas não foi registrada no sistema!";}
            
            estado.execute("ROLLBACK");
            estado.close();
            render3 = true;
            return "failure";
        }
    }

    public String cadastrarNota() throws SQLException {

        tipo = "Nota";

        try {
            for (int a = 0; a < listaNotas.size(); a++) {
                estado = conexao.createStatement();
                estado.execute("BEGIN WORK");

                estado.execute("INSERT INTO avaliacao(idturma_x_discente, unidade, nota) VALUES ('" + listaNotas.get(a).getIdturma_x_discenteN() + "','" + unidade + "','" + listaNotas.get(a).getNota() + "')");
                estado.execute("COMMIT");
                estado.close();
                
                
                estado = conexao.createStatement();
                rs = estado.executeQuery("SELECT * FROM turma_has_discente WHERE idturma_has_discente= '" + listaNotas.get(a).getIdturma_x_discenteN() + "'");
                if (rs.next()) {
                    matriculadisc = rs.getString(5);
                }
                rs.close();
                estado.close();
                
                texto = "Nota adicionada na disciplina: " + turma + " Nota: " + listaNotas.get(a).getNota();

                System.out.println("Teste: " + matriculadisc);

                System.out.println("Texto: " + texto);

                Docente docente;

                docente = (Docente) FacesContext.getCurrentInstance().getExternalContext().getSessionMap().get("docente");

                matriculadoc = docente.getMatriculadoc();

                System.out.println("Matricula docente: " + matriculadoc);

                estado = conexao.createStatement();

                estado.execute("INSERT INTO notificacao(discente_matriculadisc, tipo_notif_tiponotificacao, docente_matriculadoc, texto) VALUES ('"
                        + matriculadisc + "','" + tipo + "','" + matriculadoc + "','" + texto + "')");

                estado.close();


                }

        render2 = false;
        return "success";

        } catch (SQLException e) {
            this.erro = e;
            msgerro2 = erro.getLocalizedMessage();
            if (msgerro2.contains("pk_unidade")&&msgerro2.contains("unicidade"))
            {msgerro2 = "As notas dessa unidade já estão cadastradas!";}
            estado.execute("ROLLBACK");
            estado.close();
            render2 = true;
            return "failure";
        }
    }

    public List<Falta> getListaFaltas() {
        return listaFaltas;
    }

    public void setListaFaltas(List<Falta> listaFaltas) {
        this.listaFaltas = listaFaltas;
    }

    public List<Avaliacao> getListaNotas() {
        return listaNotas;
    }

    public void setListaNotas(List<Avaliacao> listaNotas) {
        this.listaNotas = listaNotas;
    }

    public String geraAlunosTurma(ValueChangeEvent event) {
        try {
            if (event.getNewValue() != event.getOldValue()) {
                ListaAlunosFaltas(event.getNewValue().toString());
                ListaAlunosNotas(event.getNewValue().toString());
            }
            return "success";
        } catch (Exception e) {
            return "failure";
        }
    }

    public String getAno() {
        return ano;
    }

    public void setAno(String ano) {
        this.ano = ano;
    }

    public String getDia() {
        return dia;
    }

    public void setDia(String dia) {
        this.dia = dia;
    }

    public String getMes() {
        return mes;
    }

    public void setMes(String mes) {
        this.mes = mes;
    }

    public String getUnidade() {
        return unidade;
    }

    public void setUnidade(String unidade) {
        this.unidade = unidade;
    }

    public String getNota() {
        return nota;
    }

    public void setNota(String nota) {
        this.nota = nota;
    }
}



